package com.xiaozhengkeji.xiaozhengblog.api;


import cn.dev33.satoken.stp.StpUtil;
import com.xiaozhengkeji.xiaozhengblog.base.entitys.ArticleClassEntity;
import com.xiaozhengkeji.xiaozhengblog.base.entitys.SystemUserEntity;
import com.xiaozhengkeji.xiaozhengblog.base.service.SystemUserEntityService;
import com.xiaozhengkeji.xiaozhengblog.bean.ResponseBean;
import com.xiaozhengkeji.xiaozhengblog.bean.type.ResCodeType;
import com.xiaozhengkeji.xiaozhengblog.events.UserLoginEvent;
import com.xiaozhengkeji.xiaozhengblog.services.bus.UserServiceBus;
import com.xiaozhengkeji.xiaozhengblog.utils.AddressesUtil;
import com.xiaozhengkeji.xiaozhengblog.utils.page.ListPager;
import com.xiaozhengkeji.xiaozhengblog.utils.page.Pagers;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.web.bind.annotation.*;
import wiki.xsx.core.util.RedisUtil;

import javax.servlet.http.HttpServletRequest;
import java.util.List;

/**
 * 用户Api
 */
@Slf4j
@RestController
@RequestMapping("/web/user")
public class UserApi {
    SystemUserEntityService systemUserEntityService;
    UserServiceBus userServiceBus;
    ApplicationContext applicationContext;

    @Autowired
    public UserApi(SystemUserEntityService systemUserEntityService, UserServiceBus userServiceBus, ApplicationContext applicationContext) {
        this.systemUserEntityService = systemUserEntityService;
        this.userServiceBus = userServiceBus;
        this.applicationContext = applicationContext;
    }

    /**
     * 用户注册
     */
    @ApiOperation("用户注册")
    @PostMapping("/register")
    public ResponseBean userRegistration(@ApiParam("用户名") @RequestParam("username") String username,
                                         @ApiParam("邮箱") @RequestParam("mailbox") String mailbox,
                                         @ApiParam("密码") @RequestParam("password") String password,
                                         @ApiParam("获取图片验证码时提交的时间戳") @RequestParam("verificationCodeTag") String verificationCodeTag,
                                         @ApiParam("图片验证码的验证码") @RequestParam("verificationCode") String verificationCode,
                                         HttpServletRequest request) {
        String redis_gcv = RedisUtil.getStringHandler().get("GVC_" + verificationCodeTag);
        if (!redis_gcv.equalsIgnoreCase(verificationCode)) {
            return new ResponseBean(ResCodeType.Error, "验证码错误!", null, 2);
        }
        RedisUtil.getStringHandler().remove("GVC_" + verificationCodeTag);
        if (userServiceBus.isUserNameOrEmailExist(username)) {
            return new ResponseBean(ResCodeType.Error, "用户名已被注册!", null, 1);
        }
        if (userServiceBus.isUserNameOrEmailExist(mailbox)) {
            return new ResponseBean(ResCodeType.Error, "邮箱已被注册!", null, 1);
        }
        //进行注册
        int ret = userServiceBus.register(username, mailbox, password, AddressesUtil.getIpAddress(request));
        if (ret == 1) {
            return new ResponseBean(ResCodeType.Success, "注册成功!", ret, null);
        } else {
            return new ResponseBean(ResCodeType.Error, "注册失败!服务器错误", ret, 2);
        }
    }

    /**
     * 验证Token的有效性
     */
    @ApiOperation("验证Token的有效性")
    @GetMapping("verifyToken")
    public ResponseBean verifyToken(@RequestParam("Token") String Token) {
        if (StpUtil.getLoginIdByToken(Token) == null) {
            return new ResponseBean(ResCodeType.Error, "Token过期!", null, null);
        }
        Integer loginID = Integer.parseInt((String) StpUtil.getLoginIdByToken(Token));
        SystemUserEntity userEntity = systemUserEntityService.selectByPrimaryKey(loginID);
        return new ResponseBean(ResCodeType.Success, "自动登录成功!", userEntity.getEmail(), null);
    }

    /**
     * 用户登录
     */
    @ApiOperation("登录")
    @PostMapping("login")
    public ResponseBean login(@ApiParam("邮箱") @RequestParam("mailbox") String mailbox,
                              @ApiParam("密码") @RequestParam("password") String password,
                              @ApiParam("获取图片验证码时提交的时间戳") @RequestParam("verificationCodeTag") String verificationCodeTag,
                              @ApiParam("图片验证码的验证码") @RequestParam("verificationCode") String verificationCode,
                              HttpServletRequest request) {
        String redis_gcv = RedisUtil.getStringHandler().get("GVC_" + verificationCodeTag);
        if (redis_gcv == null) {
            return new ResponseBean(ResCodeType.Error, "验证码过期!", null, 3);
        }
        if (!redis_gcv.equalsIgnoreCase(verificationCode)) {
            applicationContext.publishEvent(new UserLoginEvent(this, null, AddressesUtil.getIpAddress(request), "验证码错误", false));
            return new ResponseBean(ResCodeType.Error, "验证码错误!", null, 2);
        }
        RedisUtil.getStringHandler().remove("GVC_" + verificationCodeTag);
        if (!userServiceBus.loginUser(mailbox, password)) {
            applicationContext.publishEvent(new UserLoginEvent(this, null, AddressesUtil.getIpAddress(request), "用户密码错误或账户被冻结", false));
            return new ResponseBean(ResCodeType.Error, "用户密码错误或账户被冻结!", null, 2);
        }
        List<SystemUserEntity> user_entity_Base = systemUserEntityService.queryByEmail(mailbox);
        StpUtil.login(user_entity_Base.get(0).getId());
        applicationContext.publishEvent(new UserLoginEvent(this, user_entity_Base.get(0), AddressesUtil.getIpAddress(request), StpUtil.getTokenInfo().getTokenValue(), true));
        return new ResponseBean(ResCodeType.Success, "登录成功", StpUtil.getTokenInfo(), StpUtil.getTokenInfo().getTokenValue());
    }

    /**
     * 获取全部用户
     */
    @ApiOperation("获取全部用户 权限(user:author)")
    @GetMapping("getUserList")
    public ResponseBean getUserList(@ApiParam("用户名/邮箱 空为查询全部") @RequestParam("query") String query,
                                    @ApiParam("第几页") @RequestParam("pageNum") Integer pageNum,
                                    @ApiParam("每页数量") @RequestParam("pageSize") Integer pageSize) {
        List<SystemUserEntity> systemUserEntities = systemUserEntityService.queryByAll(new SystemUserEntity());
        ListPager<SystemUserEntity> systemUserEntityListPager = Pagers.newListPager(pageSize, systemUserEntities);
        return new ResponseBean(ResCodeType.Success, "!", systemUserEntityListPager.getPage(pageNum), systemUserEntities.size());
    }

}
